﻿namespace Arbalest.Web.Helpers
{
    using System;
    using System.Collections.Generic;
    using System.Data.Metadata.Edm;
    using System.Data.Objects;
    using System.Linq;
    using System.Web;

    public sealed class EntityFrameworkHelper : BaseHelper
    {
        public static ObjectSet<T> GetList<T>() where T : class
        {
            ObjectContext DbContext = new ObjectContext(ConfigurationHelper.ConnectionStrings.ArbalestEntities);
            ObjectSet<T> set = DbContext.CreateObjectSet<T>();
            return set;
        }

        public static void Remove<T>(T source) where T : class
        {
            ObjectContext DbContext = new ObjectContext(ConfigurationHelper.ConnectionStrings.ArbalestEntities);
            DbContext.AttachTo(GetEntitySetName<T>(), source);
            DbContext.ObjectStateManager.ChangeObjectState(source, System.Data.EntityState.Deleted);
            DbContext.SaveChanges();
        }

        public static void Add<T>(T source) where T : class
        {
            ObjectContext DbContext = new ObjectContext(ConfigurationHelper.ConnectionStrings.ArbalestEntities);
            DbContext.AttachTo(GetEntitySetName<T>(), source);
            DbContext.ObjectStateManager.ChangeObjectState(source, System.Data.EntityState.Added);
            DbContext.SaveChanges();
        }

        public static void Update<T>(T source) where T : class
        {
            ObjectContext DbContext = new ObjectContext(ConfigurationHelper.ConnectionStrings.ArbalestEntities);
            DbContext.AttachTo(GetEntitySetName<T>(), source);
            DbContext.ObjectStateManager.ChangeObjectState(source, System.Data.EntityState.Modified);
            DbContext.SaveChanges();

            #region comment out
            //object parsedObject;

            //var entry = DbContext.ObjectStateManager.GetObjectStateEntry(DbContext.CreateEntityKey(GetEntitySetName<T>(), source));

            //if (DbContext.TryGetObjectByKey(DbContext.CreateEntityKey(GetEntitySetName<T>(), source), out parsedObject))
            //{
            //    // Has object
            //    //DbContext.ApplyCurrentValues<T>(GetEntitySetName<T>(), source);
            //    DbContext.Detach(parsedObject);
            //}
            #endregion comment out
        }

        public static string GetEntitySetName<T>() where T : class
        {
            ObjectContext DbContext = new ObjectContext(ConfigurationHelper.ConnectionStrings.ArbalestEntities);

            string entitySetName = string.Empty;

            
            EntityContainer entityContainer = DbContext.MetadataWorkspace.GetEntityContainer(
                "ArbalestEntities", DataSpace.CSpace);

            string setName = entityContainer
                .BaseEntitySets
                .Where(set => set.ElementType.Name == typeof(T).Name)
                .FirstOrDefault()
                .Name;

            entitySetName = string.Format("{0}.{1}", entityContainer.Name, setName);

            return entitySetName;

            #region Original - comment out
            //ToREMOVE: After 3months after 2013-04-01

            //string className = typeof(T).Name;
            //EntityContainer container = DbContext.MetadataWorkspace.GetEntityContainer(
            //    "ArbalestEntities", DataSpace.CSpace);

            //string setName = (from meta in container.BaseEntitySets
            //                  where meta.ElementType.Name == className
            //                  select meta.Name).First();

            //entitySetName = string.Format("{0}.{1}",
            //   container.Name, setName);
            #endregion Original - comment out
        }

        #region comment out
        // Some code to enumerate entitycontainers (among other stuff)
        //public static void GetI()
        //{
        //    ObjectContext DbContext = new ObjectContext(ConfigurationHelper.ConnectionStrings.ArbalestEntities);
        //    DbContext.MetadataWorkspace.GetItems<EntityContainer>(DataSpace.SSpace);

        //    //OSpace	Represents the default name for the object model.
        //    //CSpace	Represents the default name for the conceptual model.
        //    //SSpace	Represents the default name for the storage model.
        //    //OCSpace	Represents the default name for the mapping between the object model and the conceptual model.
        //    //CSSpace	Represents the default name for the mapping between the conceptual model and the storage model.
        //    DbContext.MetadataWorkspace.GetItems(DataSpace.SSpace);
        //    GlobalItem a;
        //}
        #endregion comment out
    }
}